from MingZhuInfo import MingZhuInfo
from typing import List
from Gong import Gong
from  CalcCore import CalcCore
from CommonVarRule import *
from Star import *
import json

class ZiWeiPan:

    # 获取天盘排布
    @staticmethod
    def getTianPanLayout(ming_zao:MingZhuInfo):
        """
        天盘排布核心方法
        流程：
            1. 获取寅首  
            2. 十二宫天干

            3. 获取命宫和身宫
            4. 获取五行局
            5. 安命主星安身主星
            6. 获取紫微星所在宫位
            7. 获取十四主星排布
            8. 十四副星排布
            9. 杂星
        """
        if ming_zao is None:
            raise ValueError("无命造信息")

        pure_gong = Gong.GetPureShiErGong()

        # 1. 获取寅首
        yin_shou_tian_gan = CalcCore.GetYanShouByTianGan(ming_zao.yearTianGan)

        # 2. 十二宫天干
        twelve_gong_tian_gan = CalcCore.GetTwelveGongTianGan(yin_shou_tian_gan)

        for i in range(12):
            t_gan = twelve_gong_tian_gan[i]
            t_di_zhi = t_gan[1]
            # 查找对应地支的宫位
            for gong in pure_gong:
                if gong.GongDiZhi == t_di_zhi:
                    gong.gong_tian_gan = t_gan[0]
                    gong.gong_ganzhi = t_gan  # 宫干支
                    break

        monthNo = CommonVarRule.MONTH_No_MAP[ming_zao.monthName]
        hourNo = CommonVarRule.DiZhi_No_MAP[ming_zao.hourName]
        dayNo = CommonVarRule.SHENRI_NO_MAP[ming_zao.dayName]

        # 获取命宫和身宫
        ming_shen_gong = CalcCore.GetMingGongAndShenGong(monthNo, hourNo)
        m = next((t for t in pure_gong if t.GongDiZhi == ming_shen_gong[0]), None)
        m.GongName = "命宫"

        # 查找身宫
        m1 = next((t for t in pure_gong if t.GongDiZhi == ming_shen_gong[1]), None)
        m1.IsShenGong = True

        # 排布十二宫位
        tmp_di_zhi_name = m.GongDiZhi
        for i in range(12):
            t_gong_wei_name = CommonVarRule.CONST_SHIERGONG[i]
            if i == 0:
                continue

            tmp_di_zhi_name = CommonVarRule.DiZhiMoveBefore(tmp_di_zhi_name)
            tent = next((t for t in pure_gong if t.GongDiZhi == tmp_di_zhi_name), None)
            tent.GongName = t_gong_wei_name

        # 五行局
        wuxing_ju = CalcCore.GetWuXingJu(m.gong_tian_gan, m.GongDiZhi)
        ming_zao.WuXingJu = wuxing_ju

        # 设置阳男阴女
        MingZhuInfo.SetSexName(ming_zao)

        # 安命主星和身主星
        ming_zao.MingZhuXing = CalcCore.GetMingZhuXing(m.GongDiZhi)
        ming_zao.ShenZhuXing = CalcCore.GetShenZhuXing(ming_zao.yearDiZhi)

        # 获取紫微星所在宫位(地支)
        ziWeiDiZhi = CalcCore.GetZiWeiXingAtGongWei(ming_zao.dayName, ming_zao.WuXingJu)
        # 获取十四主星排布
        shiZhuxing = CalcCore.Get_ShiSiZhuXingLayout(ziWeiDiZhi)

        # 十四主星
        for di_zhi, stars in shiZhuxing.items():
            # 查找对应地支的宫位
            tent = next((t for t in pure_gong if t.GongDiZhi == di_zhi), None)
            if tent:
                gStars = tent.stars_list
                for star_name in stars:
                    # 创建1级星并添加到宫位中
                    gStars.append(Star.CreateStar(star_name, 1))

        return pure_gong

    @staticmethod
    def to_json(pure_gong: List[Gong]) -> str:
        """
        将宫位列表转换为JSON格式

        Args:
            pure_gong: 宫位列表

        Returns:
            str: JSON字符串
        """

        def serialize_star(star: Star):
            """序列化单个星曜"""
            return {
                "StarName": star.StarName,
                "StarLevel": star.StarLevel,
                "SiHuaXing": star.SiHuaXing,
                "WuXingAttr": star.WuXingAttr,
                "LightLevel": star.LightLevel,
                "YinYangAttr": star.YinYangAttr.name if star.YinYangAttr else None,
                "PrimaryCatelog": (
                    star.PrimaryCatelog.name if star.PrimaryCatelog else None
                ),
                "StarTypes": [t.name for t in star.StarTypes] if star.StarTypes else [],
            }

        def serialize_gong(gong: Gong):
            """序列化单个宫位"""
            return {
                "GongName": gong.GongName,
                "GongDiZhi": gong.GongDiZhi,
                "gong_tian_gan": gong.gong_tian_gan,
                "gong_ganzhi": gong.gong_ganzhi,
                "is_shen_gong": gong.is_shen_gong,
                "stars_list": [serialize_star(star) for star in gong.stars_list],
            }

        gong_list = [serialize_gong(gong) for gong in pure_gong]
        return json.dumps(gong_list, ensure_ascii=False, indent=2)


if __name__ == "__main__":
    mingzao = MingZhuInfo().GetMingZhuXing("1990", "5", "4", "卯", "男", "张三")
    print(mingzao)
    pure_gong= ZiWeiPan.getTianPanLayout(mingzao)

    # 输出JSON格式
    json_output = ZiWeiPan.to_json(pure_gong)
    print(json_output)
